import React, { PureComponent } from 'react';

import { generate as generateId } from 'shortid';
import { isEqual, set } from 'lodash';
import { Button, Icon } from 'antd';
import { CSSTransition, TransitionGroup } from 'react-transition-group';
import styles from './DynamicFilter.less';
// component
import BtnSwitch from '@/components/SwitchTool/BtnSwitch';
import ConnectionForm from '@/components/FormTools/ConnectionForm';

const revOptionName = optionItem => {
  const eventName = optionItem.event_name;
  const { groupName, name } = optionItem;
  const setVal = `${groupName}.${eventName ? `${eventName}.` : ''}${name}`;
  return setVal;
};

// conditions:条件

const RenderFilterInput = ({ $conditions, $propertyList, onDeleteItem, onChange, $onGetParams, funcConfig, groupName, groups }) => (
  <TransitionGroup>
    {$conditions.map((item, index) => (
      <CSSTransition timeout={150} classNames="scale" key={item.key || index}>
        <div key={item.key || index} className={`${styles.filterFormItem} clearfix`}>
          <div className={styles.filterInput}>
            <ConnectionForm
              defaultValue={item}
              funcConfig={funcConfig}
              options={$propertyList}
              groupName={groupName}
              groups={groups}
              getParams={$onGetParams}
              onChange={value => {
                onChange(value, index);
              }}
            ></ConnectionForm>
          </div>
          <div className={styles.filterOpthion}>
            <Button
              onClick={() => {
                onDeleteItem(index);
              }}
              type="primary"
              shape="circle"
              size="small"
            >
              <Icon type="close"></Icon>
            </Button>
          </div>
        </div>
      </CSSTransition>
    ))}
  </TransitionGroup>
);

class DynamicFilter extends PureComponent {
  static getDerivedStateFromProps(nextProps, preState) {
    if (!nextProps.value || isEqual(nextProps.value, preState.value)) {
      return null;
    }
    return {
      value: nextProps.value || nextProps.defaultValue,
      data: nextProps.value || nextProps.defaultValue
    };
  }

  constructor(props) {
    super(props);
    const { defaultValue, value } = this.props;
    const $value = value || defaultValue || { conditions: [], relation: 'and' };
    this.state = {
      data: {
        ...$value
      },
      value: {
        ...$value
      }
    };
  }

  // componentWillReceiveProps(nextProps) {
  //   this.setState({
  //     data: nextProps.defaultValue
  //   });
  // }

  /**
   * @description 删除一行过滤项
   * @memberof DynamicFilter
   */
  deleteItem = index => {
    const {
      data: { conditions }
    } = this.state;
    conditions.splice(index, 1);
    this.setState(
      oldState => ({
        data: { ...oldState.data }
      }),
      () => {
        this.actionChange();
      }
    );
  };

  /**
   * @description 条件切换事件
   * @param {*} value
   */
  handleRelationChange = value => {
    const $state = set(this.state, 'data.relation', value);
    this.setState($state, () => {
      this.actionChange();
    });
  };

  /**
   * @description 过滤联动组件值改变
   * @memberof DynamicFilter
   */
  connectionFormOnChange = (valueObj, index) => {
    const { data } = this.state;
    const oldCondithion = data.conditions[index];
    data.conditions[index] = { ...oldCondithion, ...valueObj };
    this.setState(
      oldState => ({
        ...oldState
      }),
      () => {
        this.actionChange(data);
      }
    );
  };

  /**
   * @description 组件值改变需要通知父级
   * @memberof DynamicFilter
   */
  actionChange = () => {
    const { onChange } = this.props;
    if (onChange) {
      const valueState = this.state.data;
      const noValueFunctions = ['isEmpty', 'isNotEmpty', 'isSet', 'notSet'];
      const conditions = valueState.conditions.filter(item => item.dataType === 'bool' || noValueFunctions.includes(item.function) || item.params.length > 0);
      const endValue = { ...valueState, conditions };
      onChange(endValue);
    }
  };

  /**
   * @description 添加一个过滤项
   */
  addFilterItem = () => {
    const { data } = this.state;
    const {
      propertyList,
      funcConfig: { config }
    } = this.props;
    const initItem = propertyList[0];
    const dataType = initItem.data_type;
    const { funcName } = config[dataType][0];
    const field = revOptionName(initItem);
    const initFilertItemInfo = {
      field,
      function: funcName,
      params: [],
      dataType,
      key: generateId()
    };
    data.conditions.push(initFilertItemInfo);
    this.setState({ data: { ...data } });
    // this.setState(oldState => ({ data: { ...oldState.data } }));
  };

  render() {
    const { data } = this.state;
    const { propertyList, onGetParams, funcConfig, groupName, groups } = this.props;
    const { handleRelationChange, deleteItem, connectionFormOnChange, addFilterItem } = this;
    return (
      <div className={styles.box}>
        <div className={styles.content}>
          {data.conditions.length ? (
            <div className={styles.filterCard}>
              {data.conditions.length > 1 && (
                <div className={styles.relationbox}>
                  <div className={styles.relationBtn}>
                    <BtnSwitch
                      // sign={index}
                      onChange={handleRelationChange}
                      defaultValue={data.relation}
                      valueList={['and', 'or']}
                      swichList={['且', '或']}
                    ></BtnSwitch>
                  </div>
                </div>
              )}
              <RenderFilterInput
                $conditions={data.conditions}
                $propertyList={propertyList}
                onDeleteItem={deleteItem}
                funcConfig={funcConfig}
                groupName={groupName}
                groups={groups}
                onChange={connectionFormOnChange}
                $onGetParams={onGetParams}
              ></RenderFilterInput>
            </div>
          ) : (
            <></>
          )}
        </div>
        <div className={styles.options}>
          <Button
            className={styles.addFilterBtn}
            onClick={() => {
              addFilterItem();
            }}
          >
            添加规则
          </Button>
        </div>
      </div>
    );
  }
}

export default DynamicFilter;
